package com.qfedu.empproject.utils;

import com.alibaba.druid.pool.DruidDataSourceFactory;

import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Objects;
import java.util.Properties;

public class DbUtils {
    // 数据源
    private static DataSource ds;
    // ThreadLocal 本地线程对象跟线程绑定的关系 可以到这个对象中设置一个Connection也可以取出来
    private static final ThreadLocal<Connection> THREAD_LOCAL = new ThreadLocal<>();

    static {
        try {
            // 在静态代码块中初始化数据源 读取数据库的配置文件
            InputStream inputStream = DbUtils.class.getResourceAsStream("/database.properties");
            Properties properties = new Properties();
            // 把配置文件中的数据库连接配置读到properties中
            properties.load(inputStream);
            // 实例化数据源
            ds = DruidDataSourceFactory.createDataSource(properties);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    // 获取连接的方法
    public static Connection getConnection() {
        Connection connection = THREAD_LOCAL.get();
        if (Objects.isNull(connection)) {
            try {
                connection = ds.getConnection();
                THREAD_LOCAL.set(connection);
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        return connection;
    }

    // 开启事务的方法
    public static void begin(){
        try {
            Connection connection = getConnection();
            connection.setAutoCommit(false);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    // 提交事务的方法
    public static void commit(){
        Connection connection = null;
        try {
            connection = getConnection();
            connection.commit();
        } catch (SQLException e) {
            e.printStackTrace();
        } finally {
            closeAll(connection,null,null);
        }
    }

    // 回滚事务的方法
    public static void rollback(){
        Connection connection = null;
        try {
            connection = getConnection();
            connection.rollback();
        } catch (SQLException e) {
            e.printStackTrace();
        } finally {
            closeAll(connection,null,null);
        }
    }

    // 关闭所有连接的方法
    public static void closeAll(Connection connection, Statement statement, ResultSet resultSet){
       try {
           if(Objects.nonNull(resultSet)){
               resultSet.close();
           }
           if(Objects.nonNull(statement)){
               statement.close();
           }
           if(Objects.nonNull(connection)){
               connection.close();
               // 从THREAD_LOCAL中移出关闭的连接
               THREAD_LOCAL.remove();
           }
       }catch (SQLException e){
           e.printStackTrace();
       }

    }
}
